package com.jiangjiang.eshop.schedule.stock;

import com.google.common.collect.Sets;
import com.jiangjiang.eshop.order.dto.OrderItemDTO;
import com.jiangjiang.eshop.schedule.domain.GoodsAllocationStockEntity;
import com.jiangjiang.eshop.schedule.domain.GoodsStockEntity;
import com.jiangjiang.eshop.schedule.domain.ScheduleGoodsAllocationStockDetail;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsAllocationStockDetailService;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsAllocationStockService;
import com.jiangjiang.eshop.schedule.service.ScheduleGoodsStockService;
import com.jiangjiang.eshop.schedule.dto.SaleDeliveryScheduleResult;
import com.jiangjiang.eshop.schedule.dto.ScheduleOrderSendOutDetailDTO;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;
import java.util.function.Function;
import java.util.stream.Collectors;

/**
 * @ClassName SubmitOrderScheduleStockUpdater
 * @Description TODO
 * @Author jhw
 * @Date 2021/8/31 7:31
 * @Version 1.0
 **/
@Component
@Scope("prototype")
@Transactional(rollbackFor = Exception.class)
public class SubmitOrderScheduleStockUpdater extends AbstractScheduleStockUpdater{

    private SaleDeliveryScheduleResult result;
    @Autowired
    private ScheduleGoodsStockService scheduleGoodsStockService;
    @Autowired
    private ScheduleGoodsAllocationStockService scheduleGoodsAllocationStockService;
    @Autowired
    private ScheduleGoodsAllocationStockDetailService scheduleGoodsAllocationStockDetailService;

    @Override
    protected void updateGoodsStock() throws Exception {
        OrderItemDTO orderItem = result.getOrderItem();
        GoodsStockEntity goodsStockEntity = scheduleGoodsStockService.queryBySkuIds(Sets.newHashSet(orderItem.getGoodsSkuId())).get(0);
        goodsStockEntity.setAvailableStockQuantity(goodsStockEntity.getAvailableStockQuantity() - orderItem.getPurchaseQuantity());
        goodsStockEntity.setLockedStockQuantity(goodsStockEntity.getLockedStockQuantity() + orderItem.getPurchaseQuantity());
        scheduleGoodsStockService.updateById(goodsStockEntity);
    }

    @Override
    protected void updateGoodsAllocationStock() throws Exception {

        //根据sku查询全部的货位库存
        Map<Long, GoodsAllocationStockEntity> allocationStockMap = scheduleGoodsAllocationStockService.queryAllBySkuId(result.getOrderItem().getGoodsSkuId())
                .stream()
                .collect(Collectors.toMap(GoodsAllocationStockEntity::getGoodsAllocationId, Function.identity()));

        // 执行库存更新逻辑
        List<GoodsAllocationStockEntity> entities = result.getPickingItems().stream().map(item -> {
            GoodsAllocationStockEntity entity = allocationStockMap.get(item.getGoodsAllocationId());
            entity.setAvailableStockQuantity(entity.getAvailableStockQuantity() - item.getPickingCount());
            entity.setLockedStockQuantity(entity.getLockedStockQuantity() + item.getPickingCount());
            return entity;
        }).collect(Collectors.toList());

        // 批量保存
         scheduleGoodsAllocationStockService.updateBatchById(entities);

    }

    @Override
    protected void updateGoodsAllocationStockDetail() throws Exception {
        // 根据id查询全部的货位库存明细数据
        Set<Long> detailIds = result.getSendOutDetails().stream()
                .map(ScheduleOrderSendOutDetailDTO::getGoodsAllocationStockDetailId)
                .collect(Collectors.toSet());
        Map<Long, ScheduleGoodsAllocationStockDetail> detailMap = scheduleGoodsAllocationStockDetailService.queryByIds(detailIds).stream()
                .collect(Collectors.toMap(ScheduleGoodsAllocationStockDetail::getId, Function.identity()));
        // 执行库存更新逻辑
        List<ScheduleGoodsAllocationStockDetail> stockDetails = result.getSendOutDetails().stream().map(detail -> {
            ScheduleGoodsAllocationStockDetail entity = detailMap.get(detail.getGoodsAllocationStockDetailId());
            entity.setCurrentStockQuantity(entity.getCurrentStockQuantity() - detail.getSendOutCount());
            entity.setLockedStockQuantity(entity.getLockedStockQuantity() + detail.getSendOutCount());
            return entity;
        }).collect(Collectors.toList());

        // 批量保存
        scheduleGoodsAllocationStockDetailService.updateBatchById(stockDetails);
    }


    @Override
    public void setParameter(Object parameter) {
        this.result = (SaleDeliveryScheduleResult) parameter;
    }
}
